package br.consultorio.digital.dao;

import java.io.BufferedReader;
import java.io.File;
import java.io.FileOutputStream;
import java.io.FileReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;

import org.ksoap2.serialization.SoapObject;

import android.app.Activity;
import android.content.Context;
import android.content.res.AssetManager;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.util.Log;
import br.consultorio.digital.dao.repositorio.SQLiteHelper;
import br.consultorio.digital.util.WebServiceCliente;

public abstract class DAO {

	private static final String DBPATH = "/data/data/br.consultorio.digital/databases/";
	private static final String DBPATHVERSAO = "/data/data/br.consultorio.digital/versao/";
	private static final String DBNAME = "bdconsultorio.db";
	private static int DBVERSION = 1;
	private static final String TAG = "DAO";
	private static boolean DBATUALIZADO = false;

	private static Cursor cursor;
	private static SQLiteDatabase database;
	private static SQLiteHelper sqlHelperDb;
	private Activity activity;

	public static void abrecriaBanco(Activity a) {
		if (database == null || !database.isOpen()) {
			try {
				DBATUALIZADO = false;

//				boolean inconexao = ConnectivityReceiver.verificaConexao(a
//						.getApplicationContext());

				if (new File(DBPATH + DBNAME).exists() == false) {
					iniciaDatabase(a);
				}

				// cria o esquema e popula a base de dados de cache.
				sqlHelperDb = new SQLiteHelper(a.getApplicationContext(),
						DBNAME, DBVERSION, new String[] {}, new String[] {});

				// cria a base de dados de produ��o
				database = a.getApplicationContext().openOrCreateDatabase(
						DBNAME, Context.MODE_WORLD_WRITEABLE, null);

				database = sqlHelperDb.getWritableDatabase();

				fechaBanco();
			} catch (Exception e) {
				Log.d(TAG, "Erro: " + e);
			}
		}
	}

	public static void fechaBanco() {
		try {
			fechaCursor();
			fechaDatabase();
			fechaHelper();
		} catch (Exception e) {
			// Log.d(TAG, "Erro: " + e);
		}
	}

	public static void fechaCursor() {
		try {
			if (cursor != null) {
				cursor.close();
			}
		} catch (Exception e) {
			// Log.d(TAG, "Erro: " + e);
		}
	}

	public static void fechaDatabase() {
		try {
			if (database != null) {
				database.close();
			}
		} catch (Exception e) {
			// Log.d(TAG, "Erro: " + e);
		}
	}

	public static void fechaHelper() {
		try {
			if (sqlHelperDb != null) {
				sqlHelperDb.close();
			}
		} catch (Exception e) {
			// Log.d(TAG, "Erro: " + e);
		}
	}

	public static void salvarVersao(int versao) {
		byte[] dados;
		try {
			if (new File(DBPATHVERSAO).exists() == false)
				new File(DBPATHVERSAO).mkdirs();

			// arq = new File(Environment.getDataDirectory(), "versao.txt");
			// transforma o texto digitado em array de bytes
			dados = (versao + "").getBytes();

			FileOutputStream fos = new FileOutputStream(DBPATHVERSAO
					+ "versao.txt");

			// escreve os dados e fecha o arquivo
			fos.write(dados);
			fos.flush();
			fos.close();
		} catch (Exception e) {
			Log.d(TAG, "Erro: " + e);
		}
	}

	public static int lerVersao() {
		File arq;
		String lstrlinha;
		int versao = 1;
		try {
			if (new File(DBPATHVERSAO).exists() == false)
				new File(DBPATHVERSAO).mkdirs();

			arq = new File(DBPATHVERSAO, "versao.txt");
			BufferedReader br = new BufferedReader(new FileReader(arq));

			// efetua uma leitura linha a linha do arquivo a carrega
			// a caixa de texto com a informa��o lida
			while ((lstrlinha = br.readLine()) != null) {
				versao = Integer.parseInt(lstrlinha);
			}
			br.close();

		} catch (Exception e) {
			Log.d(TAG, "Erro: " + e);
		}
		return versao;
	}

	/**
	 * @param context
	 * @throws IOException
	 */
	public static void iniciaDatabase(Context c) {
		if (new File(DBPATH).exists() == false)
			new File(DBPATH).mkdirs();

		OutputStream os = null;
		AssetManager am = null;
		InputStream is = null;

		try {
			os = new FileOutputStream(DBPATH + DBNAME);

			am = c.getAssets();

			is = am.open("database/BDConsultorio.db");

			byte[] b = new byte[1024];
			int r;

			while ((r = is.read(b)) != -1)
				os.write(b, 0, r);

			is.close();
			os.close();
		} catch (IOException e) {
			Log.d(TAG, "Erro: " + e);
		}
	}

	public static int verificaVersao() {
		WebServiceCliente wsc = WebServiceCliente.getinstance();
		wsc.executeServiceCliente("ObterNumeroVersao");

		return wsc.retornaInteiroPrimitivo();
	}

	public static void insereDadosCarga() {
		try {
			database.beginTransaction();

			WebServiceCliente wsc = WebServiceCliente.getinstance();
			wsc.executeServiceCliente("ObterTxDadosCarga");

			SoapObject so = wsc.retornaSoapObject();

			for (int i = 0; i < so.getPropertyCount(); i++) {
				database.execSQL(so.getProperty(i).toString());
			}

			database.setTransactionSuccessful();
		} catch (Exception erro) {
			Log.e(TAG, "Erro: " + erro);
		} finally {
			database.endTransaction();
		}
	}

	public static String getDbpath() {
		return DBPATH;
	}

	public static String getDbname() {
		return DBNAME;
	}

	public static boolean getDBATUALIZADO() {
		return DBATUALIZADO;
	}

	public static void setDBATUALIZADO(boolean dBATUALIZADO) {
		DBATUALIZADO = dBATUALIZADO;
	}

	public static Cursor getCursor() {
		return cursor;
	}

	public static void setCursor(Cursor cursor) {
		DAO.cursor = cursor;
	}

	public static SQLiteDatabase getDatabase() {
		if (database == null || !database.isOpen()) {
			database = sqlHelperDb.getWritableDatabase();
		}
		return database;
	}

	public static SQLiteHelper getSqlHelperDb() {
		return sqlHelperDb;
	}

	public static void setSqlHelperDb(SQLiteHelper sqlHelperDb) {
		DAO.sqlHelperDb = sqlHelperDb;
	}

	public static int getDBVERSION() {
		return DBVERSION;
	}

	public static void setDBVERSION(int dBVERSION) {
		DBVERSION = dBVERSION;
	}

	public Activity getActivity() {
		return activity;
	}

	public void setActivity(Activity activity) {
		this.activity = activity;
	}
}
